package com.hk.core.redis.json;


import com.hk.commons.util.ArrayUtils;
import com.hk.commons.util.Lazy;
import com.hk.commons.util.SpringContextHolder;
import com.hk.core.redis.scripting.RedisScriptSource;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.data.redis.core.script.DefaultRedisScript;


/**
 * Redis json 操作
 */
@NoArgsConstructor(access = AccessLevel.PRIVATE)
public abstract class JsonOperations {

    private static final DefaultRedisScript<String> JSON_SET_LUA_SCRIPT;

    private static final DefaultRedisScript<String> JSON_GET_LUA_SCRIPT;

    private static final DefaultRedisScript<Boolean> JSON_DEL_LUA_SCRIPT;

    private static final Lazy<StringRedisTemplate> STRING_REDIS_TEMPLATE =
            Lazy.of(() -> SpringContextHolder.getBean(StringRedisTemplate.class));

    static {
        JSON_SET_LUA_SCRIPT = new DefaultRedisScript<>();
        JSON_SET_LUA_SCRIPT.setScriptSource(RedisScriptSource.JSON_SET_LUA_SCRIPT);
        JSON_SET_LUA_SCRIPT.setResultType(String.class);

        JSON_GET_LUA_SCRIPT = new DefaultRedisScript<>();
        JSON_GET_LUA_SCRIPT.setScriptSource(RedisScriptSource.JSON_GET_LUA_SCRIPT);
        JSON_GET_LUA_SCRIPT.setResultType(String.class);


        JSON_DEL_LUA_SCRIPT = new DefaultRedisScript<>();
        JSON_DEL_LUA_SCRIPT.setScriptSource(RedisScriptSource.JSON_DEL_LUA_SCRIPT);
        JSON_DEL_LUA_SCRIPT.setResultType(Boolean.class);
    }

    /**
     * json 设置值
     * <a href="https://redis.io/docs/latest/commands/json.set/">json set 命令</a>
     */
    public static String set(String key, String path, Object value) {
        return STRING_REDIS_TEMPLATE.get().execute(JSON_SET_LUA_SCRIPT, ArrayUtils.asArrayList(key), path, value);
    }

    /**
     * json GET值
     * <a href="https://redis.io/docs/latest/commands/json.get/">json GET 命令</a>
     */
    public static String get(String key, String path) {
        return STRING_REDIS_TEMPLATE.get().execute(JSON_GET_LUA_SCRIPT, ArrayUtils.asArrayList(key), path);
    }

    /**
     * json del
     * <a href="https://redis.io/docs/latest/commands/json.del/">json del 命令</a>
     */
    public static Boolean del(String key, String path) {
        return STRING_REDIS_TEMPLATE.get().execute(JSON_DEL_LUA_SCRIPT, ArrayUtils.asArrayList(key), path);
    }
}
